﻿using Common;
using DataLibrary;
using System;
using System.Collections;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Linq.Expressions;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace ImageUploader
{
    public partial class Form_Export : Form
    {
        private ImageManagerEntities ime = new ImageManagerEntities();
        private Hashtable workshopids = new Hashtable();
        private Hashtable teamids = new Hashtable();
        private Hashtable machineids = new Hashtable();
        private Hashtable quailtyids = new Hashtable();
        private delegate void GetProcessCallBack(Label label, Button btn, ProgressBar bar, int _totle, int _cnt, string remark);
        private bool isBreak = false;
        private Expression<Func<ImageInfo, bool>> where = null;
        private Expression<Func<ImageInfo, bool>> lastwhere = null;
        private static int total = 0;
        private List<string> result = null;
        public Form_Export()
        {
            InitializeComponent();
        }

        public static void getProcess(Label label, Button btn, ProgressBar bar, int _totle, int _cnt, string remark)
        {
            _totle = total;
            if (label.InvokeRequired)
            {
                GetProcessCallBack getProcessCallBack = getProcess;
                label.Invoke(getProcessCallBack, new object[] { label, btn, bar, _totle, _cnt, remark });
            }
            label.Text = remark + _totle.ToString()+"/"+_cnt.ToString();
            bar.Minimum = 0;
            bar.Maximum = _totle;
            bar.Value = _cnt;
            if (_totle == _cnt)
            {
                btn.Enabled = true;
                label.Text = "导出完成..." + _totle.ToString() + "/" + _cnt.ToString();
            }
        }

        private void btn_Export_Click(object sender, EventArgs e)
        {
            if (string.IsNullOrEmpty(txt_ExportPath.Text))
            {
                MessageBox.Show("请选择导出路径");
                return;
            }
            isBreak = false;
            where = Condition();            
            btn_Export.Enabled = false;
            ThreadPool.SetMinThreads(5, 5); // set min thread to 5
            ThreadPool.SetMaxThreads(10, 10);// set max thread to 12
            ThreadPool.QueueUserWorkItem(new WaitCallback(download), new object());
            lb_Process.Visible = true;
        }

        public void download(object val)
        {
            ime.Configuration.LazyLoadingEnabled = false;//延时加载开关，关闭后可以避免查询关联的表数据，其实可以用select来避免这种情况                        
            if (lastwhere != where)
                total = ime.ImageInfo.AsQueryable().Where(where.Compile()).Count();
            if (total == 0)
                getProcess(lb_Process, btn_Export, progressBar1, total, 0, "检索结果为空。");
            int cnt = 0;
            if (total > 10000)
            {
                getProcess(lb_Process, btn_Export, progressBar1, total, cnt, "数据量过大，请缩小检索条件。"); 
                return;
            }
            else
            {
                if (result != null && result.Count > 0 && lastwhere == where)
                {
                    getProcess(lb_Process, btn_Export, progressBar1, total, cnt, "下载继续...");
                }
                else
                {                    
                    result = ime.ImageInfo.AsQueryable().Where(where.Compile()).Select(u => u.ImagePath).ToList();
                    //total = result.Count();
                }
                FtpArg args = new FtpArg();
                args.FtpServerIP = System.Configuration.ConfigurationManager.AppSettings["FtpServerIP"].ToString() + ":2121";
                args.FtpUserID = System.Configuration.ConfigurationManager.AppSettings["FtpUserID"].ToString();
                args.FtpPassword = System.Configuration.ConfigurationManager.AppSettings["FtpPassword"].ToString();
                foreach (string item in result)
                {
                    if (isBreak)
                    {
                        getProcess(lb_Process, btn_Export, progressBar1, total, cnt, "已暂停...");
                        break;
                    }
                    string[] parts = item.Split('\\');
                    string remotePath = parts[3] + "\\" + parts[4] + "\\" + parts[5] + "\\" + parts[6] + "\\" + parts[7] + "\\" + parts[8];
                    string localpath = Path.Combine(txt_ExportPath.Text, Path.GetFileName(item));
                    if (File.Exists(localpath))
                    {
                        cnt++;
                        getProcess(lb_Process, btn_Export, progressBar1, total, cnt, "导出中...");
                    }
                    else
                    {
                        string ftpfile = FtpHelper.GetFile2(remotePath, Path.GetFileName(item), args);
                        if (ftpfile != "-1")
                        {
                            string localfile = Path.Combine(txt_ExportPath.Text, Path.GetFileName(item));
                            FtpHelper.FtpDownloadBroken2(ftpfile, remotePath, localfile, true, 0, args);
                            cnt++;
                            getProcess(lb_Process, btn_Export, progressBar1, total, cnt, "导出中...");
                        }
                    }
                }
                lastwhere = where;
            }
        }

        private void AutoLoad()
        {
            var teams = ime.Teams;
            var workshops = ime.Workshops;
            var users = ime.Users;
            var quailtys = ime.Quality;
            List<string> teamList = new List<string>();
            List<string> workshopList = new List<string>();            
            List<string> userlist = new List<string>();
            List<string> qualitylist = new List<string>();
            teamList.Add("全部");
            workshopList.Add("全部");
            userlist.Add("全部");
            qualitylist.Add("全部");
            foreach (var team in teams)
            {
                teamList.Add(team.TeamName);
                teamids.Add(team.TeamName, team.TeamID);
            }
            
            foreach (var workshop in workshops)
            {
                workshopList.Add(workshop.Name);
                workshopids.Add(workshop.Name, workshop.WorkshopID);//反过来存
            }
            foreach (var user in users)
            {
                userlist.Add(user.UserNum);
            }
            foreach (var quailty in quailtys)
            {
                qualitylist.Add(quailty.Name);
                quailtyids.Add(quailty.Name, quailty.QualityID);
            }
            cBox_Team.DataSource = teamList;
            cBox_Workshop.DataSource = workshopList;
            cbox_User.DataSource = userlist;
            cbox_Quality.DataSource = qualitylist;
            var sourceTeam = new AutoCompleteStringCollection();
            var sourceWorkshop = new AutoCompleteStringCollection();
            var sourceUser = new AutoCompleteStringCollection();
            var sourceQuality = new AutoCompleteStringCollection();
            foreach (var name in teamList)
            {
                sourceTeam.Add(name);
            }
            foreach (var name in workshopList)
            {
                sourceWorkshop.Add(name);
            }
            foreach (var num in userlist)
            {
                sourceUser.Add(num);
            }
            foreach (var name in qualitylist)
            {
                sourceQuality.Add(name);
            }
            cbox_User.AutoCompleteCustomSource = sourceUser;
            cbox_User.AutoCompleteMode = AutoCompleteMode.SuggestAppend;
            cbox_User.AutoCompleteSource = AutoCompleteSource.CustomSource;
            cBox_Team.AutoCompleteCustomSource = sourceTeam;
            cBox_Team.AutoCompleteMode = AutoCompleteMode.SuggestAppend;
            cBox_Team.AutoCompleteSource = AutoCompleteSource.CustomSource;
            cBox_Workshop.AutoCompleteCustomSource = sourceWorkshop;
            cBox_Workshop.AutoCompleteMode = AutoCompleteMode.SuggestAppend;
            cBox_Workshop.AutoCompleteSource = AutoCompleteSource.CustomSource;
            cbox_Quality.AutoCompleteCustomSource = sourceQuality;
            cbox_Quality.AutoCompleteMode = AutoCompleteMode.SuggestAppend;
            cbox_Quality.AutoCompleteSource = AutoCompleteSource.CustomSource;
        }

        private void Form_Export_Load(object sender, EventArgs e)
        {
            AutoLoad();
        }

        private Expression<Func<ImageInfo, bool>> Condition()
        {
            var _where = LinqKit.PredicateBuilder.New<ImageInfo>(true);
            if (checkBox1.Checked)
            {
                DateTime start = DateTime.Parse(dateTimePicker1.Text);
                DateTime end = DateTime.Parse(dateTimePicker2.Text);
                _where.And(u => u.Created_at >= start && u.Created_at <= end);
            }
            string workshop = cBox_Workshop.SelectedValue.ToString();
            string team = cBox_Team.SelectedValue.ToString();
            string machineNo = cBox_MachineNo.SelectedValue.ToString();
            string user = cbox_User.SelectedValue.ToString();
            string quality = cbox_Quality.SelectedValue.ToString();
            string sns = txt_SNlist.Text;
            if (!string.IsNullOrEmpty(workshop) && !workshop.Contains("全部"))
            {
                _where.And(u => u.ImagePath.Contains(workshop));
            }
            if (!string.IsNullOrEmpty(machineNo) && !machineNo.Contains("全部"))
            {
                _where.And(u => u.MachineID == Convert.ToInt32(machineids[machineNo]));
            }
            if (!string.IsNullOrEmpty(team) && !team.Contains("全部"))
            {
                _where.And(u => u.TeamID == Convert.ToInt32(teamids[team]));
            }
            if (!string.IsNullOrEmpty(user) && !user.Contains("全部"))
            {
                _where.And(u => u.UserNum == user);
            }
            if (!string.IsNullOrEmpty(quality) && !quality.Contains("全部"))
            {
                _where.And(u => u.QualityID == Convert.ToInt32(quailtyids[team]));
            }
            if (!string.IsNullOrEmpty(sns))
            {
                List<string> snlist = null;
                if (sns.Contains('-'))
                {
                    string[] tmp = sns.Split('-');
                    string start = tmp[0];
                    string end = tmp[1];
                    int len = 0;
                    if (end.Length == start.Length)
                    {
                        //什么都不做
                    }
                    else if (end.Length == 5)
                    {
                        end = start.Substring(0, start.Length - 5) + end;
                    }
                    else
                    {
                        MessageBox.Show("序列号格式错误");
                        return null;
                    }
                    len = (int)(double.Parse(end) - double.Parse(start) + 1);
                    snlist = new List<string>(len);
                    for (int i = 0; i < len; i++)
                    {
                        string sn = (double.Parse(start) + i).ToString();
                        //_where = _where.Or(u => u.OriginPath == sn);
                        snlist.Add(sn);
                    }
                }
                else
                {
                    string[] snParts = null;
                    if (sns.Contains(','))
                        snParts = sns.Split(',');
                    else if (sns.Contains('\r'))
                        snParts = sns.Split('\r');
                    else if (sns.Contains('\n'))
                        snParts = sns.Split('\n');
                    else
                    {
                        sns = sns + ",";
                        snParts = sns.Split(',');
                    }
                    snlist = new List<string>(snParts.Count());
                    foreach (string sn in snParts)
                    {
                        snlist.Add(sn);
                    }
                }
                _where = _where.And(u => snlist.Contains(u.OriginPath));
            }
            return _where;
        }

        private void cBox_Workshop_SelectedIndexChanged(object sender, EventArgs e)
        {
            cBox_MachineNo.DataSource = null;
            string workshop = cBox_Workshop.SelectedValue.ToString();
            int workshopid = Convert.ToInt32(workshopids[workshop]);
            var machines = ime.Machines.Where(u => u.WorkshopID == workshopid);
            var sourceMachine = new AutoCompleteStringCollection();
            List<string> machineList = new List<string>();
            machineList.Add("全部");
            foreach (var machine in machines)
            {
                machineList.Add(machine.MachineNum.ToString());
            }
            cBox_MachineNo.DataSource = machineList;
        }

        private void checkBox1_CheckedChanged(object sender, EventArgs e)
        {
            if (checkBox1.Checked)
            {
                dateTimePicker1.Enabled = true;
                dateTimePicker2.Enabled = true;
            }
            else
            {
                dateTimePicker1.Enabled = false;
                dateTimePicker2.Enabled = false;
            }
        }

        private void button1_Click(object sender, EventArgs e)
        {
            isBreak = true;
            btn_Export.Enabled = true;
        }

        private void btn_SelectPath_Click(object sender, EventArgs e)
        {
            FolderBrowserDialog dialog = new FolderBrowserDialog();
            if (dialog.ShowDialog() == DialogResult.OK)
            {
                txt_ExportPath.Text = dialog.SelectedPath;
            }
        }
    }
}
